<script lang="ts" setup>
import { useUserStore } from '@/stores/user'
import { baseURL } from '@/utils/request'
// 注意：
//  ✅ @hyoga/uni-socket.io 才是兼容多端的 socket 库
//  ❌ socket.io-client 只能兼容 H5 端
import io from '@hyoga/uni-socket.io'
import RoomStatus from './components/room-status.vue'
import { getPatientConsultOrderDetailAPI } from '@/apis/consult'
import { OrderStatus, type GetPatientConsultOrderDetailData } from '@/types/consult'
import { nextTick, ref } from 'vue'
import type { ChatMsgListData, MsgItem } from '@/types/room'
import PatientInfo from './components/patient-info.vue'
import NotifyInfo from './components/notify-info.vue'
import MessageInfo from './components/message-info.vue'
import PrescriptionInfo from './components/prescription-info.vue'
import RateInfo from './components/rate-info.vue'
import { postUploadAPI } from '@/apis/common'
import { useConsultOrderDetail } from '@/hooks'
// 页面参数
const props = defineProps<{
  paryResult: 'true' | 'false'
  orderId: string
  type: string
}>()
// 创建 socket 连接
const store = useUserStore()
const socket = io(baseURL, {
  // 传递 token，用于身份认证（后端要求）
  auth: { token: `Bearer ${store.token}` },
  // 传递订单 id，用于查询订单信息（后端要求）
  query: { orderId: props.orderId },
  // 为了更好的兼容性：支持 websocket 和 轮询 两种传输方式
  transports: ['websocket', 'polling'],
  // 超时时间
  timeout: 5000,
})
const { orderDetail, getOrderDetail } = useConsultOrderDetail(props.orderId)


// 1. 监听订单状态变化，后端定义的事件名称为 statusChange
socket.on('statusChange', () => {
  // 重新获取订单详情，包含订单状态，倒计时秒数
  getOrderDetail()
})
// 消息列表
const msgList = ref<MsgItem[]>([])
//  2. 获取历史消息，后端定义的事件名称为 chatMsgList
socket.on('chatMsgList', (res: ChatMsgListData) => {
  // 业务状态码
  if (res.code !== 10000) return
  // 循环消息组（消息组按时间节点划分，一个消息组包含多个消息）
  res.data?.forEach((item) => {
    // 如果有消息列表，则追加到数组中
    if (item.items) {
      msgList.value.push(
        // 前添加一条普通消息，作为消息组的时间
        {
        msgType:31,
        msg:{
          content: item.createTime,
        },
        createTime:item.createTime,
      },
      ...item.items,
    )
    }
  })
  console.log(msgList.value)
})
//  3. 接收回复消息，后端定义的事件名称为 receiveChatMsg
socket.on('receiveChatMsg',async (res: MsgItem) => {
  // 追加到消息数组中
  msgList.value.push(res)
  // 通知后端，前端消息已读
  socket.emit('updateMsgStatus', res.id)
   // 通过 nextTick 等待消息列表更新
   await nextTick()
    // 接收消息后，滚动到最新消息
    scrollIntoViewId.value = `id-${res.id}`
})

socket.on('connect', () => {
  console.log('连接成功')
})
socket.on('disconnect', () => {
  console.log('连接失败')
})
// 4.发送消息
const textMessage = ref('')
const sendMessage = () => {
  // 空判断
  if (textMessage.value.trim() === '') {
    uni.showToast({ title: '请输入消息', icon: 'none' })
    return
  }
  // 发送消息
  socket.emit('sendChatMsg', {
    from:store.userInfo?.id,// 发送人id
    to: orderDetail.value?.docInfo?.id, // 接收人id (医生id)
    msgType: 1, // 消息类型，1 表示文字消息
    msg: {
      content: textMessage.value, // 文本消息内容
    },
  })
  //发送消息后， 清空输入框
  textMessage.value = ''
}
// 5. 发送图片消息
const handleUploadImage = async () => {
  //非咨询中状态，不能发送图片消息
  if (orderDetail.value?.status !== OrderStatus.ZiXunZhong) {
    uni.showToast({ title: '医生当前不在线!', icon: 'none' })
    return
  }
  // 选择图片（支持相册和相机）
  const { tempFilePaths } = await uni.chooseImage({
    count: 1,// 最多可以选择的图片张数
    sizeType: ['original', 'compressed'], // 可以指定是原图还是压缩图，默认二者都有
    sourceType: ['album', 'camera'],// 可以指定来源是相册还是相机，默认二者都有
  })
  // 上传图片，传递图片路径
  const res = await postUploadAPI(tempFilePaths[0])
  // console.log(res)
  // 上传成功后，发送图片消息
  socket.emit('sendChatMsg', {
    from:store.userInfo?.id,// 发送人id
    to: orderDetail.value?.docInfo?.id, // 接收人id (医生id)
    msgType: 4, // 消息类型，4 表示图片消息
    msg: {
      picture: res.data, // 文本消息内容
    },
  })
}
// 滚动到最新消息
const scrollIntoViewId = ref('')
</script>

<template>
  <view class="room-page">
    <!-- 咨询室状态组件 -->
    <RoomStatus
      v-if="orderDetail"
      :status="orderDetail?.status"
      :statusValue="orderDetail?.statusValue"
      :countdown="orderDetail?.countdown"
    />
    <!-- 消息列表 -->
    <scroll-view
      refresher-enabled
      refresher-background="#f2f2f2"
      scroll-y
      style="flex: 1; 
      overflow: hidden"
      :scroll-into-view="scrollIntoViewId"
    >
      <view class="message-container">
        <!-- 
          消息的类型
            1文字
            4图片

            21卡片-患者病情 
            22卡片-处方信息

            23未提交评价
            24已提交评价 

            31通知-普通通知（白底黑色）
            32通知-温馨提示
            33通知-订单取消（灰色底黑字）
        -->
        <!-- 此处将来填充更多代码... -->
        <view v-for="item in msgList" :key="item.id" :id="`id-${item.id}`">
          <!-- 患者信息 -->
          <PatientInfo v-if="item.msgType === 21" :info="item.msg?.consultRecord" />
          <!-- 通知信息，普通通知（31）和温馨提示（32） -->
          <NotifyInfo v-else-if="item.msgType && item.msgType >= 31" :type="item.msgType">
            {{ item.msg?.content }}
          </NotifyInfo>
          <!-- 气泡消息 -->
          <MessageInfo v-else-if="item.msgType === 1 || item.msgType === 4" :message="item" />
          <!-- 处方信息 -->
          <PrescriptionInfo v-else-if="item.msgType === 22" :info="item.msg?.prescription!" />
          <!-- 医生评价 -->
          <RateInfo
            :order-id="props.orderId"
            :doctor-id="orderDetail?.docInfo?.id"
            v-if="item.msgType === 23"
          />
          <!-- 医生评价（已评价） -->
          <RateInfo
            :evaluateDoc="item.msg?.evaluateDoc"
            has-evaluate
            v-else-if="item.msgType === 24"
          />
        </view>
      </view>
    </scroll-view>

    <!-- 发送消息 -->
    <view class="message-bar">
      <template v-if="true">
        <uni-easyinput
          v-model="textMessage"
          @confirm="sendMessage"
          :disabled="orderDetail?.status !== OrderStatus.ZiXunZhong"
          :clearable="false"
          :input-border="false"
          placeholder-style="font-size: 32rpx; color: #c3c3c5;"
          placeholder="问医生"
        />
        <view class="image-button" @click="handleUploadImage">
          <uni-icons size="40" color="#979797" type="image"></uni-icons>
        </view>
      </template>
      <button v-else class="uni-button">咨询其它医生</button>
    </view>
  </view>
</template>

<style lang="scss">
@import './index.scss';
</style>
